﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Data.Common;
using System.Web;
using System.Reflection;
using System.Data.Objects.DataClasses;
using System.Linq;

namespace P2PWeb.Models.Reporsitory
{
    public static class AnonymousTypeConversion
    {

        /// <summary>
        /// Converts a single DbDataRwcord object into something else.
        /// The destination type must have a default constructor.
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="record"></param>
        /// <returns></returns>
        public static T ConvertTo<T>(this DbDataRecord record)
        {
            T item = Activator.CreateInstance<T>();
            for (int f = 0; f < record.FieldCount; f++)
            {
                PropertyInfo p = item.GetType().GetProperty(record.GetName(f));
                if (p != null /*&& p.PropertyType == record.GetFieldType(f)*/)
                {
                    p.SetValue(item, record.GetValue(f) == System.DBNull.Value ? "" : record.GetValue(f), null);
                }
            }
            return item;
        }


        /// <summary>
        /// Converts a list of DbDataRecord to a list of something else.
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="list"></param>
        /// <returns></returns>
        public static List<T> ConvertTo<T>(this List<DbDataRecord> list)
        {
            List<T> result = (List<T>)Activator.CreateInstance<List<T>>();
            list.ForEach(rec =>
            {
                result.Add(rec.ConvertTo<T>());
            });
            return result;
        }

        public static string ConvertToJson(this DbDataRecord record)
        {

            StringBuilder json = new StringBuilder();
            for (int i = 0; i < record.FieldCount; i++)
            {
                if (json.Length != 0)
                    json.Append(",");
                string value = record.GetValue(i) == System.DBNull.Value ? "" : record.GetValue(i).ToString();
                json.AppendFormat("{0}:\"{1}\"", record.GetName(i), HttpUtility.HtmlEncode(value));
            }
            return json.Insert(0, "{").Append("}").ToString();
        }

        public static string ConvertToJson(this List<DbDataRecord> list)
        {
            StringBuilder json = new StringBuilder();
            list.ForEach(rec =>
            {
                if (json.Length != 0)
                    json.Append(",");
                json.Append(rec.ConvertToJson());
            });
            return json.Insert(0, "{data:[").Append("]}").ToString();
        }


        public static string ConvertToJson<T>(this T entity, string propertyList)
        {
            StringBuilder json = new StringBuilder();
            Type type = entity.GetType();
            string[] propertyArray = propertyList.Split(',');
            for (int i = 0; i < propertyArray.Length; i++)
            {
                PropertyInfo _PropertyInfo = type.GetProperty(propertyArray[i]);
                string propertyName = propertyArray[i];
                string propertyValue = GetPropertyValue(entity, propertyArray[i]);
                if (json.Length != 0)
                    json.Append(",");
                json.AppendFormat("{0}:\"{1}\"", propertyName, propertyValue);
            }
            return json.Insert(0, "{").Append("}").ToString();
        }

        public static string GetPropertyValue(object obj, string property)
        {
            Type type = obj.GetType();
            string propertyName = "";
            if (property.IndexOf(".") > -1)
                propertyName = property.Substring(0, property.IndexOf("."));
            else
                propertyName = property;
            PropertyInfo _PropertyInfo = type.GetProperty(propertyName);
            if (_PropertyInfo == null)
                return "";
            var propertyValue = _PropertyInfo.GetValue(obj, null);
            if (propertyName == property)
            {
                if (propertyValue == System.DBNull.Value || propertyValue == null)
                    return "";
                else return
                    propertyValue.ToString();
            }
            else
            {
                property = property.Remove(0, property.IndexOf(".") + 1);
                if (_PropertyInfo.PropertyType.Name == "EntityCollection`1")
                {
                    StringBuilder json = new StringBuilder();
                    foreach (Object p in (IRelatedEnd)propertyValue)
                    {
                        //过滤删除项
                        Type typep = p.GetType();
                        PropertyInfo isDel = type.GetProperty("IsDel");
                        if (Convert.ToBoolean(isDel.GetValue(p, null)))
                            continue;

                        if (json.Length != 0)
                            json.Append(",");
                        json.Append(GetPropertyValue(p, property));
                    }
                    if (json.Length == 0)
                        return "";
                    else
                        return json.Insert(0, "[").Append("]").ToString();
                }
                else
                {

                    return GetPropertyValue(propertyValue, property);
                }
            }
        }


        public static string ConvertToJson<T>(this List<T> list, string propertyList)
        {
            StringBuilder json = new StringBuilder();
            List<string> tmpresult = new List<string>();
            list.ForEach(obj =>

                tmpresult.Add(obj.ConvertToJson(propertyList))
            );
            var result = tmpresult.Distinct();
            foreach (string t in result)
            {
                if (json.Length != 0)
                    json.Append(",");
                json.Append(t);
            }
            return json.Insert(0, "{data:[").Append("]}").ToString();
        }


    }

}